<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>仪表板编辑 - AI数据分析助手</title>
    <link href="./assets/bootstrap.min.css" rel="stylesheet">
    <link rel="stylesheet" href="./assets/gridstack.min.css">
    <link href="./assets/fontawesome.min.css" rel="stylesheet">
    <script src="./assets/plotly-latest.min.js"></script>
    <style>
        body {
            background-color: #f8f9fa;
            font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
        }
        .navbar {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            position: relative;
        }
        
        .navbar::after {
            content: '编辑模式';
            position: absolute;
            top: 50%;
            left: 50%;
            transform: translate(-50%, -50%);
            background: rgba(255, 255, 255, 0.2);
            color: white;
            padding: 0.25rem 0.75rem;
            border-radius: 15px;
            font-size: 0.8rem;
            font-weight: 600;
            backdrop-filter: blur(10px);
        }
        .navbar-brand {
            font-weight: bold;
            color: white !important;
        }
        .dashboard-header {
            background: white;
            border-radius: 10px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            margin-bottom: 20px;
            padding: 20px;
        }
        .chart-container {
            background: white;
            border-radius: 10px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            padding: 15px;
            height: 100%;
            overflow: hidden;
        }
        .chart-title {
            font-size: 16px;
            font-weight: bold;
            margin-bottom: 10px;
            color: #333;
            border-bottom: 2px solid #667eea;
            padding-bottom: 5px;
        }
        .grid-stack {
            background: transparent;
        }
        .grid-stack-item-content {
            background: white;
            border-radius: 10px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            padding: 15px;
            overflow: hidden;
        }
        .btn-primary {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            border: none;
            border-radius: 25px;
            padding: 8px 20px;
        }
        .btn-primary:hover {
            transform: translateY(-2px);
            box-shadow: 0 4px 15px rgba(102, 126, 234, 0.4);
        }
        .sidebar {
            background: white;
            border-radius: 10px;
            box-shadow: 0 2px 10px rgba(0,0,0,0.1);
            padding: 20px;
            height: calc(100vh - 200px);
            overflow-y: auto;
        }
        .chart-item {
            background: #f8f9fa;
            border: 1px solid #dee2e6;
            border-radius: 8px;
            padding: 10px;
            margin-bottom: 10px;
            cursor: pointer;
            transition: all 0.3s ease;
        }
        .chart-item:hover {
            background: #e9ecef;
            transform: translateY(-2px);
            box-shadow: 0 4px 10px rgba(0,0,0,0.1);
        }
        .dashboard-item {
            background: #f8f9fa;
            border: 1px solid #dee2e6;
            border-radius: 8px;
            padding: 15px;
            margin-bottom: 15px;
            cursor: pointer;
            transition: all 0.3s ease;
        }
        .dashboard-item:hover {
            background: #e9ecef;
            transform: translateY(-2px);
            box-shadow: 0 4px 10px rgba(0,0,0,0.1);
        }
        .dashboard-item.active {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
        }
        .loading {
            text-align: center;
            padding: 3rem;
            color: #6c757d;
        }
        .loading .spinner-border {
            width: 3rem;
            height: 3rem;
            border-width: 0.3em;
        }
        .loading .loading-text {
            margin-top: 1rem;
            font-size: 1.1rem;
            font-weight: 500;
        }
        .empty-state {
            text-align: center;
            padding: 4rem 2rem;
            background: linear-gradient(135deg, #f8f9fa 0%, #e9ecef 100%);
            border-radius: 15px;
            border: 2px dashed #dee2e6;
            margin: 1rem 0;
        }
        .empty-state i {
            font-size: 4rem;
            margin-bottom: 1.5rem;
            color: #667eea;
            opacity: 0.7;
        }
        .empty-state h4 {
            color: #495057;
            font-weight: 600;
            margin-bottom: 1rem;
        }
        .empty-state p {
            color: #6c757d;
            font-size: 1rem;
            margin-bottom: 1.5rem;
        }
        .error-state {
            text-align: center;
            padding: 3rem 2rem;
            background: linear-gradient(135deg, #fff5f5 0%, #fed7d7 100%);
            border-radius: 15px;
            border: 2px solid #feb2b2;
            margin: 1rem 0;
        }
        .error-state i {
            font-size: 3rem;
            margin-bottom: 1rem;
            color: #e53e3e;
        }
        .error-state h5 {
            color: #c53030;
            font-weight: 600;
            margin-bottom: 0.5rem;
        }
        .error-state p {
            color: #9b2c2c;
            margin-bottom: 0;
        }
        
        /* 浮动查看模式按钮 */
        .view-mode-btn {
            position: fixed;
            bottom: 2rem;
            right: 2rem;
            background: linear-gradient(135deg, #4facfe 0%, #00f2fe 100%);
            color: white;
            border: none;
            border-radius: 50px;
            padding: 1rem 1.5rem;
            font-weight: 600;
            box-shadow: 0 10px 30px rgba(79, 172, 254, 0.3);
            transition: all 0.3s ease;
            z-index: 1000;
            text-decoration: none;
            display: flex;
            align-items: center;
            gap: 0.5rem;
        }
        
        .view-mode-btn:hover {
            transform: translateY(-3px);
            box-shadow: 0 15px 35px rgba(79, 172, 254, 0.4);
            color: white;
            text-decoration: none;
        }
    </style>
</head>
<body>
    <!-- 导航栏 -->
    <nav class="navbar navbar-expand-lg">
        <div class="container-fluid">
            <a class="navbar-brand text-white" href="/">
                <i class="fas fa-edit me-2"></i>
                AI数据分析助手 - 仪表板编辑
            </a>
            <div class="navbar-nav ms-auto">
                <a class="nav-link text-white" href="dashboard_view.html">
                    <i class="fas fa-eye me-1"></i>
                    查看模式
                </a>
                <a class="nav-link text-white" href="index.html">
                    <i class="fas fa-home me-1"></i>
                    返回首页
                </a>
                <a class="nav-link text-white" href="chat.html">
                    <i class="fas fa-comments me-1"></i>
                    AI对话
                </a>
            </div>
        </div>
    </nav>

    <div class="container-fluid mt-4">
        <div class="row">
            <!-- 左侧边栏 -->
            <div class="col-md-3">
                <div class="sidebar">
                    <!-- 仪表板列表 -->
                    <div class="mb-4">
                        <div class="d-flex justify-content-between align-items-center mb-3">
                            <h5 class="mb-0">
                                <i class="fas fa-tachometer-alt me-2"></i>
                                仪表板
                            </h5>
                            <button class="btn btn-primary btn-sm" onclick="createDashboard()">
                                <i class="fas fa-plus"></i>
                            </button>
                        </div>
                        <div id="dashboardList">
                            <div class="loading">
                                <div class="spinner-border text-primary" role="status">
                                    <span class="visually-hidden">Loading...</span>
                                </div>
                                <div class="loading-text">正在加载仪表板...</div>
                            </div>
                        </div>
                    </div>

                    <!-- 图表库 -->
                    <div>
                        <h5 class="mb-3">
                            <i class="fas fa-chart-bar me-2"></i>
                            图表库
                        </h5>
                        <div id="chartList">
                            <div class="loading">
                                <div class="spinner-border text-primary" role="status">
                                    <span class="visually-hidden">Loading...</span>
                                </div>
                                <div class="loading-text">正在加载图表库...</div>
                            </div>
                        </div>
                    </div>
                </div>
            </div>

            <!-- 主内容区域 -->
            <div class="col-md-9">
                <div class="dashboard-header">
                    <div class="d-flex justify-content-between align-items-center">
                        <div>
                            <h3 id="dashboardTitle">选择一个仪表板</h3>
                            <p id="dashboardDescription" class="text-muted mb-0">从左侧选择一个仪表板开始编辑</p>
                        </div>
                        <div>
                            <button id="saveLayoutBtn" class="btn btn-primary" onclick="saveDashboardLayout()" style="display: none;">
                                <i class="fas fa-save me-2"></i>
                                保存布局
                            </button>
                        </div>
                    </div>
                </div>

                <!-- 仪表板网格 -->
                <div id="dashboardGrid">
                    <div class="empty-state">
                        <i class="fas fa-tachometer-alt"></i>
                        <h4>欢迎使用仪表板编辑器</h4>
                        <p>从左侧选择一个仪表板开始编辑，或点击 <strong>+</strong> 按钮创建新的仪表板</p>
                        <div class="mt-3">
                            <button class="btn btn-outline-primary btn-sm" onclick="createDashboard()">
                                <i class="fas fa-plus me-2"></i>创建第一个仪表板
                            </button>
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>

    <!-- 浮动查看模式按钮 -->
    <a href="dashboard_view.html" class="view-mode-btn">
        <i class="fas fa-eye"></i>
        查看模式
    </a>

    <!-- 创建仪表板模态框 -->
    <div class="modal fade" id="createDashboardModal" tabindex="-1">
        <div class="modal-dialog">
            <div class="modal-content">
                <div class="modal-header">
                    <h5 class="modal-title">创建新仪表板</h5>
                    <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
                </div>
                <div class="modal-body">
                    <form id="createDashboardForm">
                        <div class="mb-3">
                            <label for="dashboardName" class="form-label">仪表板名称</label>
                            <input type="text" class="form-control" id="dashboardName" required>
                        </div>
                        <div class="mb-3">
                            <label for="dashboardDesc" class="form-label">描述</label>
                            <textarea class="form-control" id="dashboardDesc" rows="3"></textarea>
                        </div>
                    </form>
                </div>
                <div class="modal-footer">
                    <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
                    <button type="button" class="btn btn-primary" onclick="submitCreateDashboard()">创建</button>
                </div>
            </div>
        </div>
    </div>

    <!-- 编辑仪表板模态框 -->
    <div class="modal fade" id="editDashboardModal" tabindex="-1">
        <div class="modal-dialog">
            <div class="modal-content">
                <div class="modal-header">
                    <h5 class="modal-title">编辑仪表板</h5>
                    <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
                </div>
                <div class="modal-body">
                    <form id="editDashboardForm">
                        <div class="mb-3">
                            <label for="editDashboardName" class="form-label">仪表板名称</label>
                            <input type="text" class="form-control" id="editDashboardName" required>
                        </div>
                        <div class="mb-3">
                            <label for="editDashboardDesc" class="form-label">描述</label>
                            <textarea class="form-control" id="editDashboardDesc" rows="3"></textarea>
                        </div>
                    </form>
                </div>
                <div class="modal-footer">
                    <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
                    <button type="button" class="btn btn-primary" onclick="submitEditDashboard()">保存</button>
                </div>
            </div>
        </div>
    </div>

    <!-- 编辑图表模态框 -->
    <div class="modal fade" id="editChartModal" tabindex="-1">
        <div class="modal-dialog">
            <div class="modal-content">
                <div class="modal-header">
                    <h5 class="modal-title">编辑图表</h5>
                    <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
                </div>
                <div class="modal-body">
                    <form id="editChartForm">
                        <div class="mb-3">
                            <label for="editChartTitle" class="form-label">图表标题</label>
                            <input type="text" class="form-control" id="editChartTitle" required>
                        </div>
                        <div class="mb-3">
                            <label for="editChartDescription" class="form-label">描述</label>
                            <textarea class="form-control" id="editChartDescription" rows="3"></textarea>
                        </div>
                    </form>
                </div>
                <div class="modal-footer">
                    <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">取消</button>
                    <button type="button" class="btn btn-primary" onclick="submitEditChart()">保存</button>
                </div>
            </div>
        </div>
    </div>

    <!-- Toast 容器 -->
    <div class="toast-container position-fixed top-0 end-0 p-3" style="z-index: 9999;"></div>

    <!-- JavaScript -->
    <script src="./assets/bootstrap.bundle.min.js"></script>
    <script src="./assets/gridstack-all.js"></script>
    
    <script>
        let grid;
        let currentDashboard = null;
        let charts = [];
        let dashboards = [];

        // Toast 提示函数
        function showToast(message, type = 'info') {
            const toastContainer = document.querySelector('.toast-container');
            const toastId = 'toast-' + Date.now();
            
            // 设置不同类型的样式
            let bgClass = 'bg-primary';
            let iconClass = 'fas fa-info-circle';
            
            switch(type) {
                case 'success':
                    bgClass = 'bg-success';
                    iconClass = 'fas fa-check-circle';
                    break;
                case 'error':
                    bgClass = 'bg-danger';
                    iconClass = 'fas fa-exclamation-circle';
                    break;
                case 'warning':
                    bgClass = 'bg-warning';
                    iconClass = 'fas fa-exclamation-triangle';
                    break;
            }
            
            const toastHtml = `
                <div id="${toastId}" class="toast align-items-center text-white ${bgClass} border-0" role="alert" aria-live="assertive" aria-atomic="true">
                    <div class="d-flex">
                        <div class="toast-body">
                            <i class="${iconClass} me-2"></i>${message}
                        </div>
                        <button type="button" class="btn-close btn-close-white me-2 m-auto" data-bs-dismiss="toast" aria-label="Close"></button>
                    </div>
                </div>
            `;
            
            toastContainer.insertAdjacentHTML('beforeend', toastHtml);
            
            const toastElement = document.getElementById(toastId);
            const toast = new bootstrap.Toast(toastElement, {
                autohide: true,
                delay: type === 'error' ? 5000 : 3000
            });
            
            toast.show();
            
            // 清理已隐藏的 toast
            toastElement.addEventListener('hidden.bs.toast', function() {
                toastElement.remove();
            });
        }

        // 初始化页面
        document.addEventListener('DOMContentLoaded', function() {
            loadDashboards();
            loadCharts();
        });

        // 加载仪表板列表
        async function loadDashboards() {
            try {
                const response = await fetch('/api/v0/dashboards');
                const data = await response.json();
                
                if (data.type === 'dashboard_list') {
                    dashboards = data.dashboards;
                    renderDashboardList();
                } else {
                    console.error('加载仪表板失败:', data.error);
                }
            } catch (error) {
                console.error('加载仪表板失败:', error);
                document.getElementById('dashboardList').innerHTML = `
                    <div class="error-state">
                        <i class="fas fa-exclamation-triangle"></i>
                        <h5>加载失败</h5>
                        <p>无法连接到服务器，请检查网络连接后重试</p>
                        <button class="btn btn-outline-danger btn-sm mt-2" onclick="loadDashboards()">
                            <i class="fas fa-redo me-2"></i>重新加载
                        </button>
                    </div>
                `;
            }
        }

        // 渲染仪表板列表
        function renderDashboardList() {
            const container = document.getElementById('dashboardList');
            
            if (dashboards.length === 0) {
                container.innerHTML = `
                    <div class="empty-state">
                        <i class="fas fa-tachometer-alt"></i>
                        <h4>暂无仪表板</h4>
                        <p>您还没有创建任何仪表板</p>
                        <button class="btn btn-primary btn-sm" onclick="createDashboard()">
                            <i class="fas fa-plus me-2"></i>创建第一个仪表板
                        </button>
                    </div>
                `;
                return;
            }

            container.innerHTML = dashboards.map(dashboard => `
                <div class="dashboard-item" onclick="loadDashboard('${dashboard.id}')">
                    <div class="d-flex justify-content-between align-items-start">
                        <div class="flex-grow-1">
                            <div class="fw-bold">${dashboard.name}</div>
                            <small class="text-muted">${dashboard.description || '无描述'}</small>
                            <div class="text-muted mt-1">
                                <small><i class="fas fa-clock me-1"></i>${new Date(dashboard.created_at).toLocaleDateString()}</small>
                            </div>
                        </div>
                        <div class="dropdown" onclick="event.stopPropagation();">
                            <button class="btn btn-sm btn-outline-secondary dropdown-toggle" type="button" data-bs-toggle="dropdown" style="padding: 2px 6px; font-size: 12px;">
                                <i class="fas fa-ellipsis-v"></i>
                            </button>
                            <ul class="dropdown-menu dropdown-menu-end">
                                <li><a class="dropdown-item" href="#" onclick="editDashboard('${dashboard.id}')"><i class="fas fa-edit me-2"></i>编辑</a></li>
                                <li><a class="dropdown-item text-danger" href="#" onclick="deleteDashboard('${dashboard.id}')"><i class="fas fa-trash me-2"></i>删除</a></li>
                            </ul>
                        </div>
                    </div>
                </div>
            `).join('');
        }

        // 加载图表列表
        async function loadCharts() {
            try {
                const response = await fetch('/api/v0/charts');
                const data = await response.json();
                
                if (data.type === 'chart_list') {
                    charts = data.charts;
                    renderChartList();
                } else {
                    console.error('加载图表失败:', data.error);
                }
            } catch (error) {
                console.error('加载图表失败:', error);
                document.getElementById('chartList').innerHTML = `
                    <div class="error-state">
                        <i class="fas fa-exclamation-triangle"></i>
                        <h5>加载失败</h5>
                        <p>无法加载图表库，请稍后重试</p>
                        <button class="btn btn-outline-danger btn-sm mt-2" onclick="loadCharts()">
                            <i class="fas fa-redo me-2"></i>重新加载
                        </button>
                    </div>
                `;
            }
        }

        // 渲染图表列表
        function renderChartList() {
            const container = document.getElementById('chartList');
            
            if (charts.length === 0) {
                container.innerHTML = `
                    <div class="empty-state">
                        <i class="fas fa-chart-bar"></i>
                        <h4>暂无图表</h4>
                        <p>您还没有保存任何图表</p>
                        <a href="chat.html" class="btn btn-outline-primary btn-sm">
                            <i class="fas fa-comments me-2"></i>去创建图表
                        </a>
                    </div>
                `;
                return;
            }

            container.innerHTML = charts.map(chart => `
                <div class="chart-item" draggable="true" ondragstart="dragStart(event, '${chart.id}')" onclick="previewChart('${chart.id}')">
                    <div class="d-flex justify-content-between align-items-start">
                        <div class="flex-grow-1">
                            <div class="fw-bold">${chart.title}</div>
                            <small class="text-muted">${chart.chart_type}</small>
                            <div class="text-muted mt-1">
                                <small><i class="fas fa-clock me-1"></i>${new Date(chart.created_at).toLocaleDateString()}</small>
                            </div>
                        </div>
                        <div class="dropdown" onclick="event.stopPropagation();">
                            <button class="btn btn-sm btn-outline-secondary dropdown-toggle" type="button" data-bs-toggle="dropdown" style="padding: 2px 6px; font-size: 12px;">
                                <i class="fas fa-ellipsis-v"></i>
                            </button>
                            <ul class="dropdown-menu dropdown-menu-end">
                                <li><a class="dropdown-item" href="#" onclick="editChart('${chart.id}')"><i class="fas fa-edit me-2"></i>编辑</a></li>
                                <li><a class="dropdown-item text-danger" href="#" onclick="deleteChart('${chart.id}')"><i class="fas fa-trash me-2"></i>删除</a></li>
                            </ul>
                        </div>
                    </div>
                </div>
            `).join('');
        }

        // 创建仪表板
        function createDashboard() {
            const modal = new bootstrap.Modal(document.getElementById('createDashboardModal'));
            modal.show();
        }

        // 提交创建仪表板
        async function submitCreateDashboard() {
            const name = document.getElementById('dashboardName').value;
            const description = document.getElementById('dashboardDesc').value;
            
            if (!name.trim()) {
                showToast('请输入仪表板名称', 'warning');
                return;
            }

            try {
                const response = await fetch('/api/v0/dashboards', {
                    method: 'POST',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({
                        name: name.trim(),
                        description: description.trim()
                    })
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 关闭模态框
                    const modal = bootstrap.Modal.getInstance(document.getElementById('createDashboardModal'));
                    modal.hide();
                    
                    // 清空表单
                    document.getElementById('createDashboardForm').reset();
                    
                    // 重新加载仪表板列表
                    await loadDashboards();
                    
                    // 自动加载新创建的仪表板
                    loadDashboard(data.dashboard_id);
                } else {
                    showToast('创建仪表板失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('创建仪表板失败:', error);
                showToast('创建仪表板失败，请检查网络连接', 'error');
            }
        }

        // 加载仪表板
        async function loadDashboard(dashboardId) {
            try {
                const response = await fetch(`/api/v0/dashboards/${dashboardId}`);
                const data = await response.json();
                
                if (data.type === 'dashboard_detail') {
                    currentDashboard = data.dashboard;
                    renderDashboard();
                    
                    // 更新选中状态
                    document.querySelectorAll('.dashboard-item').forEach(item => {
                        item.classList.remove('active');
                    });
                    // 通过dashboardId找到对应的dashboard-item并设置为active
                    const targetItem = document.querySelector(`[onclick="loadDashboard('${dashboardId}')"]`);
                    if (targetItem) {
                        targetItem.classList.add('active');
                    }
                } else {
                    console.error('加载仪表板失败:', data.error);
                }
            } catch (error) {
                console.error('加载仪表板失败:', error);
            }
        }

        // 渲染仪表板
        function renderDashboard() {
            if (!currentDashboard) return;

            // 更新标题
            document.getElementById('dashboardTitle').textContent = currentDashboard.name;
            document.getElementById('dashboardDescription').textContent = currentDashboard.description || '无描述';
            document.getElementById('saveLayoutBtn').style.display = 'block';

            // 初始化网格
            const gridContainer = document.getElementById('dashboardGrid');
            gridContainer.innerHTML = '<div class="grid-stack"></div>';
            
            const gridElement = gridContainer.querySelector('.grid-stack');
            grid = GridStack.init({
                cellHeight: 80,
                margin: 10,
                acceptWidgets: true,
                removable: false,
                resizable: {
                    handles: 'e, se, s, sw, w'
                },
                minRow: 1 // 确保至少有一行
            }, gridElement);

            // 添加现有图表
            if (currentDashboard.charts) {
                currentDashboard.charts.forEach(chartItem => {
                    const pos = chartItem.position;
                    addChartToGrid(chartItem, pos.x, pos.y, pos.width, pos.height);
                });
            }

            // 设置拖放事件
            setupDragAndDrop();
        }

        // 设置拖放
        function setupDragAndDrop() {
            const gridEl = document.querySelector('.grid-stack');
            
            gridEl.addEventListener('dragover', function(e) {
                e.preventDefault();
            });
            
            gridEl.addEventListener('drop', function(e) {
                e.preventDefault();
                const chartId = e.dataTransfer.getData('text/plain');
                const chart = charts.find(c => c.id === chartId);
                
                if (chart) {
                    // 检查图表是否已存在于当前仪表板
                    if (isChartInDashboard(chartId)) {
                        showToast('该图表已存在于当前仪表板中，无法重复添加', 'warning');
                        return;
                    }
                    addChartToGrid(chart, 0, 0, 6, 4);
                    addChartToDashboard(chartId, 0, 0, 6, 4);
                }
            });
        }

        // 拖拽开始
        function dragStart(event, chartId) {
            event.dataTransfer.setData('text/plain', chartId);
        }

        // 预览图表
        function previewChart(chartId) {
            const chart = charts.find(c => c.id === chartId);
            if (!chart) return;

            // 创建预览模态框
            const modalHtml = `
                <div class="modal fade" id="chartPreviewModal" tabindex="-1">
                    <div class="modal-dialog modal-xl">
                        <div class="modal-content">
                            <div class="modal-header">
                                <h5 class="modal-title">${chart.title}</h5>
                                <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
                            </div>
                            <div class="modal-body">
                                <div class="mb-3">
                                    <strong>类型:</strong> ${chart.chart_type}<br>
                                    <strong>创建时间:</strong> ${new Date(chart.created_at).toLocaleString()}<br>
                                    ${chart.description ? `<strong>描述:</strong> ${chart.description}<br>` : ''}
                                    ${chart.question ? `<strong>问题:</strong> ${chart.question}<br>` : ''}
                                </div>
                                <div id="previewChart" style="height: 600px; border: 1px solid #dee2e6; border-radius: 0.375rem;"></div>
                            </div>
                            <div class="modal-footer">
                                <button type="button" class="btn btn-secondary" data-bs-dismiss="modal">关闭</button>
                                ${currentDashboard ? `<button type="button" class="btn btn-primary" onclick="addChartFromPreview('${chart.id}')">添加到仪表板</button>` : ''}
                            </div>
                        </div>
                    </div>
                </div>
            `;

            // 移除已存在的预览模态框
            const existingModal = document.getElementById('chartPreviewModal');
            if (existingModal) {
                existingModal.remove();
            }

            // 添加新的预览模态框
            document.body.insertAdjacentHTML('beforeend', modalHtml);

            // 显示模态框
            const modal = new bootstrap.Modal(document.getElementById('chartPreviewModal'));
            modal.show();

            // 渲染图表预览
            setTimeout(() => {
                renderChartPreview(chart);
            }, 300);
        }

        // 渲染图表预览
        function renderChartPreview(chart) {
            const container = document.getElementById('previewChart');
            if (!container) return;

            try {
                if (chart.chart_type === 'plotly') {
                    // 统一使用chart_config字段，处理双重JSON编码
                    let chartData;
                    const configData = chart.chart_config || chart.data_config;
                    if (typeof configData === 'string') {
                        // 第一次解析
                        let parsedData = JSON.parse(configData);
                        // 如果结果还是字符串，再次解析
                        if (typeof parsedData === 'string') {
                            chartData = JSON.parse(parsedData);
                        } else {
                            chartData = parsedData;
                        }
                    } else {
                        chartData = configData;
                    }
                    Plotly.newPlot(container, chartData.data, chartData.layout, {
                        responsive: true,
                        displayModeBar: true
                    });
                } else if (chart.chart_type === 'table') {
                    let tableData;
                    const configData = chart.chart_config || chart.data_config;
                    if (typeof configData === 'string') {
                        // 第一次解析
                        let parsedData = JSON.parse(configData);
                        // 如果结果还是字符串，再次解析
                        if (typeof parsedData === 'string') {
                            tableData = JSON.parse(parsedData);
                        } else {
                            tableData = parsedData;
                        }
                    } else {
                        tableData = configData;
                    }
                    
                    // 处理HTML转义问题
                    let htmlContent = tableData;
                    if (typeof htmlContent === 'string') {
                        // 解码HTML实体
                        const tempDiv = document.createElement('div');
                        tempDiv.innerHTML = htmlContent;
                        htmlContent = tempDiv.innerHTML;
                    }
                    
                    container.innerHTML = `<div style="overflow: auto; height: 100%; padding: 10px;">${htmlContent}</div>`;
                }
            } catch (error) {
                console.error('渲染图表预览失败:', error);
                container.innerHTML = '<div class="d-flex align-items-center justify-content-center h-100 text-muted">图表预览失败</div>';
            }
        }

        // 从预览添加图表到仪表板
        function addChartFromPreview(chartId) {
            if (!currentDashboard) return;

            // 检查图表是否已存在于当前仪表板
            if (isChartInDashboard(chartId)) {
                showToast('该图表已存在于当前仪表板中，无法重复添加', 'warning');
                return;
            }

            // 关闭预览模态框
            const modal = bootstrap.Modal.getInstance(document.getElementById('chartPreviewModal'));
            modal.hide();

            // 添加图表到网格
            const chart = charts.find(c => c.id === chartId);
            if (chart) {
                addChartToGrid(chart, 0, 0, 6, 4);
                addChartToDashboard(chartId, 0, 0, 6, 4);
            }
        }

        // 检查图表是否已存在于当前仪表板
        function isChartInDashboard(chartId) {
            if (!currentDashboard || !currentDashboard.charts) {
                return false;
            }
            return currentDashboard.charts.some(chartItem => chartItem.id === chartId);
        }

        // 添加图表到网格
        function addChartToGrid(chart, x, y, w, h) {
            const widget = grid.addWidget({
                x: x,
                y: y,
                w: w,
                h: h
            });
            setTimeout(() => {
                const contentDiv = widget.querySelector('.grid-stack-item-content');
                if (contentDiv) {
                    contentDiv.innerHTML = `
                        <div class="chart-container">
                            <div class="chart-title-container" style="position: relative; display: flex; align-items: center; justify-content: space-between; padding: 5px 10px; background: #f8f9fa; border-bottom: 1px solid #dee2e6;">
                                <div class="chart-title" 
                                     data-chart-id="${chart.id}" 
                                     style="flex: 1; cursor: pointer; padding: 2px 5px; border-radius: 3px;" 
                                     ondblclick="editChartTitle('${chart.id}')" 
                                     title="双击编辑标题">${chart.title}</div>
                                <div class="chart-actions" style="display: flex; gap: 5px;">
                                    <button class="btn btn-sm btn-outline-secondary" 
                                            onclick="editChartTitle('${chart.id}')" 
                                            title="编辑标题" 
                                            style="padding: 2px 6px; font-size: 12px;">
                                        <i class="fas fa-edit"></i>
                                    </button>
                                    <button class="btn btn-sm btn-outline-danger" 
                                            onclick="removeChartFromDashboard('${chart.id}')" 
                                            title="删除图表" 
                                            style="padding: 2px 6px; font-size: 12px;">
                                        <i class="fas fa-trash"></i>
                                    </button>
                                </div>
                            </div>
                            <div id="chart-${chart.id}" style="height: calc(100% - 50px);"></div>
                        </div>
                    `;
                    setTimeout(() => {
                        renderChart(chart);
                    }, 100);
                }
            }, 100);

            // 渲染图表
            setTimeout(() => {
                const widget = grid.getGridItems().find(item => item.getAttribute('gs-id') === String(chart.id));
                if (widget) {
                    const contentDiv = widget.querySelector('.grid-stack-item-content');
                    if (contentDiv) {
                        contentDiv.innerHTML = `
                            <div class="chart-container">
                                <div class="chart-title-container" style="position: relative; display: flex; align-items: center; justify-content: space-between; padding: 5px 10px; background: #f8f9fa; border-bottom: 1px solid #dee2e6;">
                                    <div class="chart-title" 
                                         data-chart-id="${chart.id}" 
                                         style="flex: 1; cursor: pointer; padding: 2px 5px; border-radius: 3px;" 
                                         ondblclick="editChartTitle('${chart.id}')" 
                                         title="双击编辑标题">${chart.title}</div>
                                    <div class="chart-actions" style="display: flex; gap: 5px;">
                                        <button class="btn btn-sm btn-outline-secondary" 
                                                onclick="editChartTitle('${chart.id}')" 
                                                title="编辑标题" 
                                                style="padding: 2px 6px; font-size: 12px;">
                                            <i class="fas fa-edit"></i>
                                        </button>
                                        <button class="btn btn-sm btn-outline-danger" 
                                                onclick="removeChartFromDashboard('${chart.id}')" 
                                                title="删除图表" 
                                                style="padding: 2px 6px; font-size: 12px;">
                                            <i class="fas fa-trash"></i>
                                        </button>
                                    </div>
                                </div>
                                <div id="chart-${chart.id}" style="height: calc(100% - 50px);"></div>
                            </div>
                        `;
                        setTimeout(() => {
                            renderChart(chart);
                        }, 100);
                    }
                }
            }, 100);
        }

        // 渲染图表
        function renderChart(chart) {
            const container = document.getElementById(`chart-${chart.id}`);
            if (!container) return;

            console.log('开始渲染图表:', chart.id, chart.title);
            console.log('图表类型:', chart.chart_type);
            console.log('原始data_config类型:', typeof chart.data_config);
            console.log('原始data_config内容:', chart.data_config);

            try {
                if (chart.chart_type === 'plotly') {
                    // 统一使用chart_config字段，处理双重JSON编码
                    let chartData;
                    const configData = chart.chart_config || chart.data_config;
                    if (typeof configData === 'string') {
                        // 第一次解析
                        let parsedData = JSON.parse(configData);
                        console.log('第一次解析结果类型:', typeof parsedData);
                        console.log('第一次解析结果:', parsedData);
                        
                        // 如果结果还是字符串，再次解析
                        if (typeof parsedData === 'string') {
                            chartData = JSON.parse(parsedData);
                            console.log('第二次解析结果:', chartData);
                        } else {
                            chartData = parsedData;
                        }
                    } else {
                        chartData = configData;
                    }
                    
                    console.log('最终chartData:', chartData);
                    console.log('chartData.data:', chartData.data);
                    console.log('chartData.layout:', chartData.layout);
                    
                    Plotly.newPlot(container, chartData.data, chartData.layout, {
                        responsive: true,
                        displayModeBar: false
                    }).then(() => {
                        console.log('Plotly图表渲染成功:', chart.id);
                    }).catch(err => {
                        console.error('Plotly渲染失败:', err);
                        container.innerHTML = '<div class="text-center text-muted">Plotly渲染失败: ' + err.message + '</div>';
                    });
                } else if (chart.chart_type === 'table') {
                    let tableData;
                    const configData = chart.chart_config || chart.data_config;
                    if (typeof configData === 'string') {
                        // 第一次解析
                        let parsedData = JSON.parse(configData);
                        // 如果结果还是字符串，再次解析
                        if (typeof parsedData === 'string') {
                            tableData = JSON.parse(parsedData);
                        } else {
                            tableData = parsedData;
                        }
                    } else {
                        tableData = configData;
                    }
                    
                    // 处理HTML转义问题
                    let htmlContent = tableData;
                    if (typeof htmlContent === 'string') {
                        // 解码HTML实体
                        const tempDiv = document.createElement('div');
                        tempDiv.innerHTML = htmlContent;
                        htmlContent = tempDiv.innerHTML;
                    }
                    
                    container.innerHTML = `
                        <div style="overflow: auto; height: 100%; padding: 10px; border: 1px solid #dee2e6; border-radius: 8px;">
                            ${htmlContent}
                        </div>
                    `;
                }
            } catch (error) {
                console.error('渲染图表失败:', error);
                console.error('错误详情:', error.stack);
                container.innerHTML = '<div class="text-center text-muted">图表渲染失败: ' + error.message + '</div>';
            }
        }

        // 添加图表到仪表板
        async function addChartToDashboard(chartId, x, y, w, h) {
            if (!currentDashboard) return;

            try {
                const response = await fetch(`/api/v0/dashboards/${currentDashboard.id}/charts`, {
                    method: 'POST',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({
                        chart_id: chartId,
                        position_x: x,
                        position_y: y,
                        width: w,
                        height: h
                    })
                });

                const data = await response.json();
                
                if (data.type !== 'success') {
                    console.error('添加图表到仪表板失败:', data.error);
                }
            } catch (error) {
                console.error('添加图表到仪表板失败:', error);
            }
        }

        // 编辑图表标题
        function editChartTitle(chartId) {
            const titleElement = document.querySelector(`[data-chart-id="${chartId}"]`);
            if (!titleElement) return;

            const currentTitle = titleElement.textContent;
            const input = document.createElement('input');
            input.type = 'text';
            input.value = currentTitle;
            input.style.cssText = 'width: 100%; border: 1px solid #007bff; border-radius: 3px; padding: 2px 5px; font-size: inherit;';
            
            // 替换标题元素为输入框
            titleElement.style.display = 'none';
            titleElement.parentNode.insertBefore(input, titleElement);
            input.focus();
            input.select();

            // 保存标题的函数
            const saveTitle = async () => {
                const newTitle = input.value.trim();
                if (newTitle && newTitle !== currentTitle) {
                    try {
                        const response = await fetch(`/api/v0/charts/${chartId}/title`, {
                            method: 'PUT',
                            headers: {
                                'Content-Type': 'application/json'
                            },
                            body: JSON.stringify({ title: newTitle })
                        });

                        const data = await response.json();
                        if (data.type === 'success') {
                            titleElement.textContent = newTitle;
                            // 更新charts数组中的标题
                            const chart = charts.find(c => c.id === chartId);
                            if (chart) {
                                chart.title = newTitle;
                            }
                        } else {
                            showToast('更新标题失败: ' + data.error, 'error');
                        }
                    } catch (error) {
                        console.error('更新标题失败:', error);
                        showToast('更新标题失败，请检查网络连接', 'error');
                    }
                }
                
                // 恢复标题显示
                input.remove();
                titleElement.style.display = 'block';
            };

            // 取消编辑的函数
            const cancelEdit = () => {
                input.remove();
                titleElement.style.display = 'block';
            };

            // 绑定事件
            input.addEventListener('blur', saveTitle);
            input.addEventListener('keydown', (e) => {
                if (e.key === 'Enter') {
                    e.preventDefault();
                    saveTitle();
                } else if (e.key === 'Escape') {
                    e.preventDefault();
                    cancelEdit();
                }
            });
        }

        // 从仪表板删除图表
        async function removeChartFromDashboard(chartId) {
            if (!currentDashboard) return;

            if (!confirm('确定要从仪表板中删除这个图表吗？')) {
                return;
            }

            try {
                const response = await fetch(`/api/v0/dashboards/${currentDashboard.id}/charts/${chartId}`, {
                    method: 'DELETE'
                });

                const data = await response.json();
                if (data.type === 'success') {
                    // 从网格中移除图表
                    const chartElement = document.getElementById(`chart-${chartId}`);
                    if (chartElement) {
                        const gridItem = chartElement.closest('.grid-stack-item');
                        if (gridItem) {
                            grid.removeWidget(gridItem);
                        }
                    }
                } else {
                    showToast('删除图表失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('删除图表失败:', error);
                showToast('删除图表失败，请检查网络连接', 'error');
            }
        }

        // 保存仪表板布局
        async function saveDashboardLayout() {
            if (!currentDashboard || !grid) return;

            const layout = [];
            grid.getGridItems().forEach(item => {
                const node = item.gridstackNode;
                const chartId = item.querySelector('[id^="chart-"]').id.replace('chart-', '');
                
                layout.push({
                    chart_id: chartId,
                    position_x: node.x,
                    position_y: node.y,
                    width: node.w,
                    height: node.h
                });
            });

            try {
                const response = await fetch(`/api/v0/dashboards/${currentDashboard.id}/layout`, {
                    method: 'PUT',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({
                        layout: layout
                    })
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 显示成功提示
                    const btn = document.getElementById('saveLayoutBtn');
                    const originalText = btn.innerHTML;
                    btn.innerHTML = '<i class="fas fa-check me-2"></i>已保存';
                    btn.classList.add('btn-success');
                    btn.classList.remove('btn-primary');
                    
                    setTimeout(() => {
                        btn.innerHTML = originalText;
                        btn.classList.remove('btn-success');
                        btn.classList.add('btn-primary');
                    }, 2000);
                } else {
                    showToast('保存布局失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('保存布局失败:', error);
                showToast('保存布局失败，请检查网络连接', 'error');
            }
        }

        // 编辑仪表板
        let editingDashboardId = null;
        function editDashboard(dashboardId) {
            const dashboard = dashboards.find(d => d.id === dashboardId);
            if (!dashboard) return;

            editingDashboardId = dashboardId;
            document.getElementById('editDashboardName').value = dashboard.name;
            document.getElementById('editDashboardDesc').value = dashboard.description || '';
            
            const modal = new bootstrap.Modal(document.getElementById('editDashboardModal'));
            modal.show();
        }

        // 提交编辑仪表板
        async function submitEditDashboard() {
            if (!editingDashboardId) return;

            const name = document.getElementById('editDashboardName').value;
            const description = document.getElementById('editDashboardDesc').value;
            
            if (!name.trim()) {
                showToast('请输入仪表板名称', 'warning');
                return;
            }

            try {
                const response = await fetch(`/api/v0/dashboards/${editingDashboardId}`, {
                    method: 'PUT',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({
                        name: name.trim(),
                        description: description.trim()
                    })
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 关闭模态框
                    const modal = bootstrap.Modal.getInstance(document.getElementById('editDashboardModal'));
                    modal.hide();
                    
                    // 重新加载仪表板列表
                    await loadDashboards();
                    
                    // 如果当前编辑的是正在显示的仪表板，更新标题
                    if (currentDashboard && currentDashboard.id === editingDashboardId) {
                        currentDashboard.name = name.trim();
                        currentDashboard.description = description.trim();
                        document.getElementById('dashboardTitle').textContent = currentDashboard.name;
                        document.getElementById('dashboardDescription').textContent = currentDashboard.description || '无描述';
                    }
                    
                    editingDashboardId = null;
                } else {
                    showToast('编辑仪表板失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('编辑仪表板失败:', error);
                showToast('编辑仪表板失败，请检查网络连接', 'error');
            }
        }

        // 删除仪表板
        async function deleteDashboard(dashboardId) {
            const dashboard = dashboards.find(d => d.id === dashboardId);
            if (!dashboard) return;

            if (!confirm(`确定要删除仪表板 "${dashboard.name}" 吗？此操作不可撤销。`)) {
                return;
            }

            try {
                const response = await fetch(`/api/v0/dashboards/${dashboardId}`, {
                    method: 'DELETE'
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 如果删除的是当前显示的仪表板，清空显示
                    if (currentDashboard && currentDashboard.id === dashboardId) {
                        currentDashboard = null;
                        document.getElementById('dashboardTitle').textContent = '选择一个仪表板';
                        document.getElementById('dashboardDescription').textContent = '从左侧选择一个仪表板开始编辑';
                        document.getElementById('saveLayoutBtn').style.display = 'none';
                        document.getElementById('dashboardGrid').innerHTML = `
                            <div class="empty-state">
                                <i class="fas fa-tachometer-alt"></i>
                                <h4>欢迎使用仪表板编辑器</h4>
                                <p>从左侧选择一个仪表板开始编辑，或点击 <strong>+</strong> 按钮创建新的仪表板</p>
                                <div class="mt-3">
                                    <button class="btn btn-outline-primary btn-sm" onclick="createDashboard()">
                                        <i class="fas fa-plus me-2"></i>创建第一个仪表板
                                    </button>
                                </div>
                            </div>
                        `;
                    }
                    
                    // 重新加载仪表板列表
                    await loadDashboards();
                } else {
                    showToast('删除仪表板失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('删除仪表板失败:', error);
                showToast('删除仪表板失败，请检查网络连接', 'error');
            }
        }

        // 编辑图表
        let editingChartId = null;
        function editChart(chartId) {
            const chart = charts.find(c => c.id === chartId);
            if (!chart) return;

            editingChartId = chartId;
            document.getElementById('editChartTitle').value = chart.title;
            document.getElementById('editChartDescription').value = chart.description || '';
            
            const modal = new bootstrap.Modal(document.getElementById('editChartModal'));
            modal.show();
        }

        // 提交编辑图表
        async function submitEditChart() {
            if (!editingChartId) return;

            const title = document.getElementById('editChartTitle').value;
            const description = document.getElementById('editChartDescription').value;
            
            if (!title.trim()) {
                showToast('请输入图表标题', 'warning');
                return;
            }

            try {
                const response = await fetch(`/api/v0/charts/${editingChartId}`, {
                    method: 'PUT',
                    headers: {
                        'Content-Type': 'application/json'
                    },
                    body: JSON.stringify({
                        title: title.trim(),
                        description: description.trim()
                    })
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 关闭模态框
                    const modal = bootstrap.Modal.getInstance(document.getElementById('editChartModal'));
                    modal.hide();
                    
                    // 更新charts数组中的图表信息
                    const chart = charts.find(c => c.id === editingChartId);
                    if (chart) {
                        chart.title = title.trim();
                        chart.description = description.trim();
                    }
                    
                    // 重新加载图表列表
                    renderChartList();
                    
                    // 如果图表在当前仪表板中，更新标题显示
                    const titleElement = document.querySelector(`[data-chart-id="${editingChartId}"]`);
                    if (titleElement) {
                        titleElement.textContent = title.trim();
                    }
                    
                    editingChartId = null;
                } else {
                    showToast('编辑图表失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('编辑图表失败:', error);
                showToast('编辑图表失败，请检查网络连接', 'error');
            }
        }

        // 删除图表
        async function deleteChart(chartId) {
            const chart = charts.find(c => c.id === chartId);
            if (!chart) return;

            if (!confirm(`确定要删除图表 "${chart.title}" 吗？此操作不可撤销。`)) {
                return;
            }

            try {
                const response = await fetch(`/api/v0/charts/${chartId}`, {
                    method: 'DELETE'
                });

                const data = await response.json();
                
                if (data.type === 'success') {
                    // 从charts数组中移除
                    const index = charts.findIndex(c => c.id === chartId);
                    if (index > -1) {
                        charts.splice(index, 1);
                    }
                    
                    // 重新渲染图表列表
                    renderChartList();
                    
                    // 如果图表在当前仪表板中，从网格中移除
                    const chartElement = document.getElementById(`chart-${chartId}`);
                    if (chartElement) {
                        const gridItem = chartElement.closest('.grid-stack-item');
                        if (gridItem && grid) {
                            grid.removeWidget(gridItem);
                        }
                    }
                } else {
                    showToast('删除图表失败: ' + data.error, 'error');
                }
            } catch (error) {
                console.error('删除图表失败:', error);
                showToast('删除图表失败，请检查网络连接', 'error');
            }
        }
    </script>
</body>
</html>